package ast


type VariousStatement struct {
	Node                   `part:"stmt"`
	Statement  Statement   `use:"first"`
}
type Statement interface { impl(Statement) }

func (DeclAsset) impl(Statement) {}
type DeclAsset struct {
	Node
	Name     string
	Content  LoadedAsset
}
func (LoadedAsset) implBody() {}
type LoadedAsset struct {
	Path  string
	Data  [] byte
}

func (DeclEntry) impl(Statement) {}
type DeclEntry struct {
	Node            `part:"decl_entry"`
	Content  Block  `part:"block"`
}

func (DeclType) impl(Statement) {}
type DeclType struct {
	Node                         `part:"decl_type"`
	Docs        [] Doc           `list:"docs.doc+"`
	Name        Identifier       `part:"name"`
	TypeParams  [] Identifier    `list:"type_params.name*,"`
	Implements  [] RefBase       `list:"impl.ref_base*,"`
	TypeDef     VariousTypeDef   `part:"type_def"`
}

func (DeclFunction) impl(Statement) {}
type DeclFunction struct {
	Node                           `part:"decl_func"`
	Docs       [] Doc              `list:"docs.doc+"`
	Operator   bool                `option:"function.@operator"`
	Variadic   bool                `option:"variadic.@variadic"`
	Name       Identifier          `part:"name"`
	Signature  FunctionSignature   `part:"sig"`
	Body       VariousBody         `part:"body"`
}
type FunctionSignature struct {
	Node                        `part:"sig"`
	TypeParams  [] Identifier   `list:"type_params.name*,"`
	Inputs      Inputs          `part:"inputs"`
	Implicit    MaybeInputs     `part_opt:"implicit.inputs"`
	Output      Type            `part:"output.type"`
}
type MaybeInputs interface { impl(MaybeInputs) }
func (Inputs) impl(MaybeInputs) {}
type Inputs struct {
	Node                 `part:"inputs"`
	Content  RecordDef   `part:"record_def"`
}
type VariousBody struct {
	Node         `part:"body"`
	Body  Body   `use:"first"`
}
type Body interface { implBody() }
func (NativeBody) implBody() {}
type NativeBody struct {
	Node         `part:"native_body"`
	Id    Text   `part:"text"`
}

func (DeclMethod) impl(Statement) {}
type DeclMethod struct {
	Node                    `part:"decl_method"`
	Docs      [] Doc        `list:"docs.doc+"`
	Receiver  Identifier    `part:"receiver.name"`
	Name      Identifier    `part:"name"`
	Type      Type          `part:"type"`
	Body      VariousBody   `part:"body"`
}

func (DeclConst) impl(Statement) {}
type DeclConst struct {
	Node                `part:"decl_const"`
	Docs  [] Doc        `list:"docs.doc+"`
	Name  Identifier    `part:"name"`
	Type  Type          `part:"type"`
	Body  VariousBody   `part:"body"`
}

type Doc struct {
	Node               `part:"doc"`
	RawContent  Code   `content:"Doc"`
}


